/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package br.com.tbp.persitence.dao.impl;

import br.com.tbp.exception.PersistenciaException;
import br.com.tbp.model.domain.Endereco;
import br.com.tbp.persitence.GerenciadorDeConexao;
import br.com.tbp.persitence.GerenciadorDeQuery;
import br.com.tbp.persitence.dao.EnderecoDao;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;

/**
 *
 * @author lubni
 */
public class EnderecoDaoImpl implements EnderecoDao {

    private Connection conn;
    private PreparedStatement pr = null;
    private ResultSet rs = null;

    public List<Endereco> pesquisar(String cep) throws PersistenciaException {
        if ((cep == null) || (cep.isEmpty())) {
            throw new PersistenciaException("Não foi informado o código postal a pesquisar.");
        }
        List<Endereco> enderecoList = new ArrayList<Endereco>();
        try {
            conn = GerenciadorDeConexao.abreConexao();
            pr = conn.prepareStatement(GerenciadorDeQuery.getQuery("endereco.select"));
            pr.setString(1, cep);
            rs = pr.executeQuery();
            while (rs.next()) {
                Endereco endereco = new Endereco(rs.getLong("cd_logradouro"), rs.getString("ds_logradouro_nome"), rs.getString("ds_bairro_nome"),
                        rs.getString("ds_cidade_nome"), rs.getString("ds_uf_sigla"), cep);
                endereco.setCodigoBairro(rs.getInt("cd_bairro"));
                endereco.setCodigoCidade(rs.getInt("cd_cidade"));
                enderecoList.add(endereco);
            }
        } catch (SQLException sqlex) {
            StringBuilder msg = new StringBuilder("Não foi possível realizar a consulta de endereço.");
            msg.append("\nMotivo: ").append(sqlex.getMessage());
            throw new PersistenciaException(msg.toString());
        } finally {
            GerenciadorDeConexao.fechaConexao(conn, pr, rs);
        }

        return enderecoList;
    }

    public Endereco pesquisar(long id) throws PersistenciaException {
        Endereco e = null;
        try {
            conn = GerenciadorDeConexao.abreConexao();
            pr = conn.prepareStatement(GerenciadorDeQuery.getQuery("endereco.select.id"));
            pr.setLong(1, id);
            rs = pr.executeQuery();
            if (rs != null) {
                if (rs.first()) {
                    e = new Endereco(rs.getLong("cd_logradouro"), rs.getString("ds_logradouro_nome"), rs.getString("ds_bairro_nome"),
                            rs.getString("ds_cidade_nome"), rs.getString("ds_uf_sigla"), rs.getString("no_logradouro_cep"));
                    e.setCodigoBairro(rs.getInt("cd_bairro"));
                    e.setCodigoCidade(rs.getInt("cd_cidade"));
                }
            }

        } catch (SQLException sqlex) {
            StringBuilder msg = new StringBuilder("Não foi possível realizar a consulta de endereço.");
            msg.append("\nMotivo: ").append(sqlex.getMessage());
            throw new PersistenciaException(msg.toString());
        } finally {
            GerenciadorDeConexao.fechaConexao(conn, pr, rs);
        }

        return e;
    }

    public void alterar(Endereco e) throws PersistenciaException {
        if (e == null) {
            throw new PersistenciaException("Não foi informado o endereço a atualizar.");
        }

        try {
            conn = GerenciadorDeConexao.abreConexao();
            pr = conn.prepareStatement(GerenciadorDeQuery.getQuery("endereco.update"));
            pr.setString(1, e.getLougradouro());
            pr.setString(2, e.getCep());
            pr.setString(3, e.getBairro());
            pr.setLong(4, e.getId());

            pr.executeUpdate();
        } catch (SQLException exc) {
            StringBuilder msg = new StringBuilder("Não foi possível atualizar o endereço.");
            msg.append("\nMotivo: ").append(exc.getMessage());
            throw new PersistenciaException(msg.toString());
        } finally {
            GerenciadorDeConexao.fechaConexao(conn, pr);
        }
    }

    public void cadastrar(Endereco e) throws PersistenciaException {
        if (e == null) {
            throw new PersistenciaException("Não foi informado o endereço a cadastrar.");
        }
        try {
            conn = GerenciadorDeConexao.abreConexao();
            pr = conn.prepareStatement("INSERT INTO LOGRADOURO(CD_LOGRADOURO, CD_BAIRRO, CD_TIPO_LOGRADOUROS, DS_LOGRADOURO_NOME, NO_LOGRADOURO_CEP) VALUES(NULL, ?, 1, ?, ?);",
                    Statement.RETURN_GENERATED_KEYS);
            pr.setInt(1, e.getCodigoBairro());
            pr.setString(2, e.getLougradouro());
            pr.setString(3, e.getCep());
            pr.executeUpdate();

            rs = pr.getGeneratedKeys();
            rs.next();
            long codigo = rs.getLong(1);
            e.setId(codigo);
        } catch (SQLException exc) {
            StringBuilder msg = new StringBuilder("Não foi possível cadastrar o endereço.");
            msg.append("\nMotivo: ").append(exc.getMessage());
            throw new PersistenciaException(msg.toString());
        } finally {
            GerenciadorDeConexao.fechaConexao(conn, pr, rs);
        }
    }

    public int cadastrarBairro(String bairro, int codigoCidade) throws PersistenciaException {
        if (bairro != null && !bairro.isEmpty()) {
            try {
                conn = GerenciadorDeConexao.abreConexao();
                pr = conn.prepareStatement("INSERT INTO BAIRRO(CD_BAIRRO, CD_CIDADE, DS_BAIRRO_NOME) VALUES(NULL, ?, ?)",
                        Statement.RETURN_GENERATED_KEYS);
                pr.setInt(1, codigoCidade);
                pr.setString(2, bairro);
                pr.executeUpdate();

                rs = pr.getGeneratedKeys();
                rs.next();
                int codigo = rs.getInt(1);
                return codigo;
            } catch (SQLException exc) {
                StringBuilder msg = new StringBuilder("Não foi possível cadastrar o bairro.");
                msg.append("\nMotivo: ").append(exc.getMessage());
                throw new PersistenciaException(msg.toString());
            } finally {
                GerenciadorDeConexao.fechaConexao(conn, pr, rs);
            }
        }
        return 0;
    }
}
